package net

import (
	"ZHONGYIHANGYAN/util/log"
	"fmt"
	"net"
	"os/exec"
	"strings"
)

var logErr, logInfo = log.GetLogger("net")

// GetIpByName 获取指定名称的网卡IP
func GetIpByName(ifaceName string) string {
	ip := ""

	interfaces, err := net.Interfaces()
	if err != nil {
		logErr.Println("获取网卡信息失败:", err)
		return ip
	}

	for _, iface := range interfaces {
		addrs, err := iface.Addrs()
		if err != nil {
			logErr.Println("获取网卡地址失败:", err)
			continue
		}
		for _, addr := range addrs {
			ipNet, ok := addr.(*net.IPNet)
			if ok && !ipNet.IP.IsLoopback() && ipNet.IP.To4() != nil {
				if iface.Name == ifaceName {
					return ipNet.IP.String()
				}
			}
		}
	}

	return ip
}

func ShowIP() {
	interfaces, err := net.Interfaces()
	if err != nil {
		logErr.Println(err)
	}

	for _, iface := range interfaces {
		if strings.Contains(iface.Flags.String(), "loopback") || iface.Name == "dummy0" {
			continue
		}
		logInfo.Printf("网卡: %v \t", iface)

		addrs, err := iface.Addrs()
		if err != nil {
			logErr.Println(err)
			continue
		}
		for _, addr := range addrs {
			ipNet, _ := addr.(*net.IPNet)
			ip := ipNet.IP.To4()
			if ip == nil {
				continue
			}
			logInfo.Printf("  名称：%s\t IP: %s\t 掩码: %s\t 私有：%t\t\n", iface.Name, ipNet.IP.To4(), net.IP(ipNet.Mask), ipNet.IP.IsPrivate())
		}
	}
	cmd := exec.Command("ip", "route")
	output, err := cmd.Output()
	if err != nil {
		logErr.Println(err)
		return
	}

	gateway := parseGateway(string(output))
	if gateway != "" {
		logInfo.Println("网关地址:", gateway)
	} else {
		logInfo.Println("未找到网关地址")
	}
}

func parseGateway(output string) string {
	lines := strings.Split(output, "\n")
	for _, line := range lines {
		fields := strings.Fields(line)
		if len(fields) >= 3 && fields[0] == "default" && fields[1] == "via" {
			return fields[2]
		}
	}
	return ""
}

type NetworkInterface struct {
	Name       string
	IP         string
	Netmask    string
	Gateway    string
	IsUp       bool
	IsRunning  bool
	IsStaticIP bool
}

func NewIP() {
	interfaces := getAllInterfaces()

	for _, iface := range interfaces {
		fmt.Printf("网卡名称: %s\n", iface.Name)
		fmt.Printf("IP 地址: %s\n", iface.IP)
		fmt.Printf("子网掩码: %s\n", iface.Netmask)
		fmt.Printf("网关地址: %s\n", iface.Gateway)
		fmt.Printf("是否启用: %t\n", iface.IsUp)
		fmt.Printf("是否运行: %t\n", iface.IsRunning)
		fmt.Printf("DHCP: %t\n\n", iface.IsStaticIP)
	}
}

func getAllInterfaces() []NetworkInterface {
	cmd := exec.Command("ip", "addr", "show")
	output, err := cmd.Output()
	if err != nil {
		logErr.Println(err)
		return nil
	}
	// fmt.Printf("aaaa: %s\n", string(output))
	lines := strings.Split(string(output), "\n")
	var interfaces []NetworkInterface
	var currentInterface NetworkInterface

	for _, line := range lines {
		fields := strings.Fields(line)
		if strings.Contains(line, "mtu") {
			if strings.Contains(line, "LOOPBACK") || strings.Contains(line, "dummy0") {
				continue
			}
			if currentInterface.Name != "" {
				interfaces = append(interfaces, currentInterface)
			}
			currentInterface = NetworkInterface{Name: strings.TrimSuffix(fields[1], ":")}
		}
		if len(fields) < 2 {
			continue
		}
		fmt.Printf("内容:%s\t数量: %d\n", line, len(fields))

		switch fields[0] {
		case "inet":
			currentInterface.IP = fields[1]
			currentInterface.IsStaticIP = true
		case "valid_lft":
			if strings.Contains(line, "dynamic") {
				currentInterface.IsStaticIP = false
			}
		case "state":
			currentInterface.IsUp = strings.Contains(line, "UP")
			currentInterface.IsRunning = strings.Contains(line, "RUNNING")
		case "brd":
			currentInterface.Gateway = fields[2]
		case "scope", "prefixlen":
			currentInterface.Netmask = fields[len(fields)-1]
		}

	}

	if currentInterface.Name != "" {
		interfaces = append(interfaces, currentInterface)
	}

	return interfaces
}

func getInfo() {
	interfaces, err := net.Interfaces()
	if err != nil {
		fmt.Println("Error:", err)
		return
	}

	for _, iface := range interfaces {
		if iface.Flags&net.FlagUp != 0 && iface.Flags&net.FlagLoopback == 0 {
			addrs, err := iface.Addrs()
			if err != nil {
				fmt.Println("Error:", err)
				return
			}

			fmt.Println("Interface Name:", iface.Name)
			fmt.Println("Interface MAC:", iface.HardwareAddr)
			fmt.Println("Interface UpDown Status:", iface.Flags&net.FlagUp != 0)
			fmt.Println("Interface Running Status:", iface.Flags&net.FlagRunning != 0)

			for _, addr := range addrs {
				ip, subnet, _ := net.ParseCIDR(addr.String())
				if ip != nil && !ip.IsLoopback() && ip.To4() != nil {
					fmt.Println("IP:", ip)
					fmt.Println("Subnet Mask:", subnet.Mask)
				}
			}

			routes, err := net.InterfaceAddrs()
			if err != nil {
				fmt.Println("Error:", err)
				return
			}

			for _, route := range routes {
				if ipnet, ok := route.(*net.IPNet); ok && !ipnet.IP.IsLoopback() {
					if ipnet.IP.To4() != nil {
						fmt.Println("Gateway:", ipnet.IP)
					}
				}
			}
			fmt.Println("--------------------------------------")
		}
	}
}
